home *** CD-ROM | disk | FTP | other *** search
/ CD ROM Paradise Collection 4 / CD ROM Paradise Collection 4 1995 Nov.iso / edit / thesrc20.zip / getch.c < prev    next >
C/C++ Source or Header  |  1995-01-26  |  13KB  |  336 lines

  1. /*
  2.  * This software is Copyright (c) 1989, 1990, 1991 by Patrick J. Wolfe.
  3.  *
  4.  * Permission is hereby granted to copy, distribute or otherwise
  5.  * use any part of this package as long as you do not try to make
  6.  * money from it or pretend that you wrote it.  This copyright
  7.  * notice must be maintained in any copy made.
  8.  *
  9.  * Use of this software constitutes acceptance for use in an AS IS
  10.  * condition. There are NO warranties with regard to this software.
  11.  * In no event shall the author be liable for any damages whatsoever
  12.  * arising out of or in connection with the use or performance of this
  13.  * software.  Any use of this software is at the user's own risk.
  14.  *
  15.  * If you make modifications to this software that you feel
  16.  * increases it usefulness for the rest of the community, please
  17.  * email the changes, enhancements, bug fixes as well as any and
  18.  * all ideas to me. This software is going to be maintained and
  19.  * enhanced as deemed necessary by the community.
  20.  *
  21.  *              Patrick J. Wolfe
  22.  *              uunet!uiucuxc!kailand!pwolfe
  23.  *              pwolfe@kailand.kai.com
  24.  *
  25.  * Additions of Xenix,Sun,DOS,VMS,AIX and OS2 key handling
  26.  * made by Mark Hessling (M.Hessling@gu.edu.au)
  27.  *
  28.  */
  29.  
  30.  
  31. /*
  32. $Id: getch.c 2.0 1995/01/26 16:31:10 MH Release MH $
  33. */
  34.  
  35. #if defined(USE_NCURSES)
  36. #   include <ncurses.h>
  37. #else
  38. #   if defined(USE_EXTCURSES)
  39. #      include <cur00.h>
  40. #   else
  41. #      include <curses.h>
  42. #   endif
  43. #endif
  44.  
  45. #if !defined(DOS) && !defined(OS2)
  46. #include "getch.h"
  47.  
  48. #define NORMAL 100
  49. #define ESCAPE 200
  50. #define FKEY   300
  51. #define BRACK  400
  52.  
  53. /***********************************************************************/
  54. #ifdef PROTO
  55. #  ifdef MSWIN
  56. int my_getch (WINDOW far *winptr)
  57. #  else
  58. int my_getch (WINDOW *winptr)
  59. #  endif
  60. #else
  61. int my_getch (winptr)
  62. #  ifdef MSWIN
  63. WINDOW far *winptr;
  64. #  else
  65. WINDOW *winptr;
  66. #  endif
  67. #endif
  68. /***********************************************************************/
  69. {
  70. /*-------------------------- external data ----------------------------*/
  71. /*--------------------------- local data ------------------------------*/
  72. int c=0;
  73. short state = NORMAL;
  74. short fkeycount = 0;
  75. /*--------------------------- processing ------------------------------*/
  76. while (1) {
  77. #ifndef VMS
  78.        c = wgetch(winptr);
  79. #else
  80.        c = keypress();
  81. #endif
  82.        switch (state) {
  83.  
  84.        case BRACK:
  85.                switch (c) {
  86.                /* Linux f1 thru f5 are <esc>[[A <esc>[[B ... <esc>[[E */
  87.                case 'A': case 'B': case 'C': case 'D': case 'E':
  88.                        return KEY_F1 + (c - 'A');
  89.                default:
  90.                        state = NORMAL;
  91.                        break;
  92.                        }
  93.                break;
  94.  
  95.        case FKEY:
  96.                switch (c) {
  97.  
  98.                /* numeric function keys */
  99.                case '0': case '1': case '2': case '3': case '4':
  100.                case '5': case '6': case '7': case '8': case '9':
  101.                        fkeycount = (fkeycount * 10) + (c - '0');
  102.                        break;
  103.  
  104.                case '~':
  105.                        switch (fkeycount) {
  106.  
  107.                        /* Find, Insert Here, Remove, Select, Prev Screen, Next Screen */
  108.                        case 1: return KEY_Find;
  109.                        case 2: return KEY_InsertHere;
  110.                        case 3: return KEY_Remove;
  111.                        case 4: return KEY_Select;
  112.                        case 5: return KEY_PrevScreen;
  113.                        case 6: return KEY_NextScreen;
  114.  
  115.                        /* unshifted xterm (Linux only ?) function keys */
  116.                        case 11: case 12: case 13: case 14: case 15:
  117.                                return KEY_F1 + (fkeycount - 11);
  118.  
  119.                        /* unshifted vt220 function keys */
  120.                        case 17: case 18: case 19: case 20: case 21:
  121.                                return KEY_F6 + (fkeycount - 17);
  122.                        case 23: case 24: case 25: case 26:
  123.                                return KEY_F11 + (fkeycount - 23);
  124.                        case 28: case 29:
  125.                                return KEY_F15 + (fkeycount - 28);
  126.                        case 31: case 32: case 33: case 34:
  127.                                return KEY_F17 + (fkeycount - 31);
  128.  
  129.                        /* vt220 function keys - control */
  130.                        case 37: case 38: case 39: case 40: case 41:
  131.                                return KEY_SF6 + (fkeycount - 37);
  132.                        case 43: case 44: case 45: case 46:
  133.                                return KEY_SF11 + (fkeycount - 43);
  134.                        case 48: case 49:
  135.                                return KEY_SF15 + (fkeycount - 48);
  136.                        case 51: case 52: case 53: case 54:
  137.                                return KEY_SF17 + (fkeycount - 51);
  138.  
  139.                        /* shifted tvs922 function keys */
  140.         /*             case 37: case 38: case 39: case 40: case 41:
  141.                        case 42: case 43: case 44: case 45: case 46:
  142.                        case 47: case 48: case 49: case 50: case 51:
  143.                                return KEY_SF6 + (fkeycount - 37); */
  144.  
  145.                        default:
  146.                                state = NORMAL;
  147.                                }
  148.                        break;
  149.  
  150.                case 'A':       return KEY_UP;
  151.                case 'B':       return KEY_DOWN;
  152.                case 'C':       return KEY_RIGHT;
  153.                case 'D':       return KEY_LEFT;
  154.                case 'M':       return KEY_PadEnter;
  155.                case 'Z':       return KEY_BackTab;
  156.  
  157.                /* Xenix default key mappings */
  158.                case 'H':       return KEY_HOME;
  159.                case 'F':       return KEY_END;
  160.                case 'L':       return KEY_InsertHere;
  161.                case 'G':       return KEY_NextScrn;
  162.                case 'I':       return KEY_PrevScrn;
  163.  
  164.                case 'N':       return KEY_F2;
  165.                case 'O':       return KEY_F3;
  166.                case 'T':       return KEY_F8;
  167.                case 'U':       return KEY_F9;
  168.                case 'V':       return KEY_F10;
  169.                case 'W':       return KEY_F11;
  170.                case 'X':       return KEY_F12;
  171.  
  172.                /* VT[12]00 PF keys */
  173.                case 'P': case 'Q': case 'R': case 'S':
  174.                        return KEY_PF1 + (c - 'P');
  175.  
  176.                /* VT[12]00 keypad */
  177.                case 'l': case 'm': case 'n': case 'o': case 'p': case 'r':
  178.                case 's': case 't': case 'u': case 'v': case 'w': case 'x': case 'y':
  179.                        return KEY_PadComma + (c - 'l');
  180.  
  181.                /* Sun Keyboard Function Keys */
  182.                case 'z':
  183.                        switch (fkeycount) {
  184.                        /* SUN F1-F10 */
  185.                        case 224: case 225: case 226: case 227: case 228:
  186.                        case 229: case 230: case 231: case 232: case 233:
  187.                                return KEY_F1 + (fkeycount - 224);
  188.                        /* SUN S-F1-S-F10 */
  189.                        case 324: case 325: case 326: case 327: case 328:
  190.                        case 329: case 330: case 331: case 332: case 333:
  191.                                return KEY_SF1 + (fkeycount - 324);
  192.                        case 192: return KEY_F11;
  193.                        case 193: return KEY_F12;
  194.                        case 195: return KEY_UNDO;
  195.                        case 292: return KEY_SF11;
  196.                        case 293: return KEY_SF12;
  197.                        case 214: return KEY_HOME;
  198.                        case 414: return KEY_CHOME;
  199.                        case 215: return KEY_UP;
  200.                        case 415: return KEY_CUP;
  201.                        case 216: return KEY_PrevScrn;
  202.                        case 416: return KEY_CPGUP;
  203.                        case 217: return KEY_LEFT;
  204.                        case 417: return KEY_CLEFT;
  205.                        case 219: return KEY_RIGHT;
  206.                        case 419: return KEY_CRIGHT;
  207.                        case 220: return KEY_END;
  208.                        case 420: return KEY_CEND;
  209.                        case 221: return KEY_DOWN;
  210.                        case 421: return KEY_CDOWN;
  211.                        case 222: return KEY_NextScrn;
  212.                        case 422: return KEY_CPGDN;
  213.                        case 1:   return KEY_BTAB;
  214.                        case 2:   return KEY_InsertHere;
  215.                        case 3:   return KEY_HOME;
  216.                        case 4:   return KEY_END;
  217.                        case 5:   return KEY_PrevScrn;
  218.                        case 6:   return KEY_NextScrn;
  219.                        case 423: return KEY_PadComma;
  220.                        default:
  221.                                state = NORMAL;
  222.                                }
  223.                        break;
  224.  
  225.                /* IBM AIX ???????? */
  226.                case 'q':
  227.                        switch (fkeycount) {
  228.                        case 0:  /* VT100/200 keypad */
  229.                                return KEY_PadComma + (c - 'l');
  230.                        /* AIX F1-F12 */
  231.                        case 1: case 2: case 3: case 4: case 5: case 6:
  232.                        case 7: case 8: case 9: case 10: case 11: case 12:
  233.                                return KEY_F1 + (fkeycount - 1);
  234.                        /* AIX SF1-F12 */
  235.                        case 13: case 14: case 15: case 16: case 17: case 18:
  236.                        case 19: case 20: case 21: case 22: case 23: case 24:
  237.                                return KEY_SF1 + (fkeycount - 13);
  238.                        /* AIX CF1-F12 */
  239.                        case 25: case 26: case 27: case 28: case 29: case 30:
  240.                        case 31: case 32: case 33: case 34: case 35: case 36:
  241.                                return KEY_CF1 + (fkeycount - 25);
  242.                        case 150: return KEY_PrevScrn;
  243.                        case 146: return KEY_END;
  244.                        case 154: return KEY_NextScrn;
  245.                        case 139: return KEY_InsertHere;
  246.                        default:
  247.                                state = NORMAL;
  248.                                }
  249.                        break;
  250.                case '[':
  251.                        state = BRACK;
  252.                        break;
  253.  
  254.                default:
  255.                        state = NORMAL;
  256.                        }
  257.                break;
  258.  
  259.        case ESCAPE:
  260.                switch (c) {
  261.                case 'O':     /* vt100 numeric keypad application codes */
  262.                case '?':     /* vt52  numeric keypad application codes */
  263.                case '[':
  264.                        state = FKEY;
  265.                        fkeycount = 0;
  266.                        break;
  267.                /* VT52 PF keys */
  268.                case 'P': case 'Q': case 'R': case 'S':
  269.                        return KEY_PF1 + (c - 'P');
  270.  
  271.                default:
  272.                        state = NORMAL;
  273.                        }
  274.                break;
  275.  
  276.        default:
  277.                switch (c) {
  278.                case Escape:
  279.                        state = ESCAPE;
  280.                        break;
  281.  
  282.                case CSI:
  283.                        state = FKEY;
  284.                        fkeycount = 0;
  285.                        break;
  286.  
  287.                default:
  288.                        return (c);
  289.                        }
  290.                }
  291.        }
  292. }
  293. #endif
  294. #if defined(DOS) || defined(OS2)
  295. int my_getch (winptr)
  296. WINDOW *winptr;
  297. {
  298.  return(wgetch(winptr));
  299. }
  300. #endif
  301. #ifdef VMS
  302. #include iodef
  303. #include descrip
  304. /***********************************************************************/
  305. short keypress()
  306. /***********************************************************************/
  307. {
  308. /*--------------------------- local data ------------------------------*/
  309. struct { long length; char *address; } logical_name;
  310. struct { short status; short length; short remainder; } iosb;
  311.  
  312. static char kb[] = { "sys$input" };
  313. static short chan;
  314.  
  315. static char key = 0;
  316. short new_key;
  317. static short first = 1;
  318. short status;
  319. /*--------------------------- processing ------------------------------*/
  320.  
  321.  key = 0;
  322.  logical_name.length = strlen (kb);
  323.  logical_name.address = kb;
  324.  status = sys$assign (&logical_name, &chan, 0, 0);
  325.  if (status != 1)
  326.    return(-1);
  327.  status = SYS$QIOW(0, chan, IO$_READVBLK | IO$M_NOFILTR | IO$M_NOECHO
  328.         | IO$M_TIMED, &iosb, 0, 0, &key, 1,600, 0,0, 0, 0);
  329.  if (!key)
  330.     return (0);
  331.  new_key = (short)(key);
  332.  status = sys$dassgn (chan);
  333.  return (new_key);
  334. }
  335. #endif
  336.